#include <iostream>
#include <event2/event.h>
#include <event2/http.h>
#include <event2/buffer.h>
#include <event2/util.h>
#include <event2/event_struct.h>
#include <cstring>
#include <pthread.h>
#include <unistd.h>
#include <event2/thread.h>
#include <signal.h>
std::string get_cmd_type(const int cmd_type){
    std::string cmdtype;
    switch (cmd_type) {
            case EVHTTP_REQ_GET: cmdtype = "GET"; break;
            case EVHTTP_REQ_POST: cmdtype = "POST"; break;
            case EVHTTP_REQ_HEAD: cmdtype = "HEAD"; break;
            case EVHTTP_REQ_PUT: cmdtype = "PUT"; break;
            case EVHTTP_REQ_DELETE: cmdtype = "DELETE"; break;
            case EVHTTP_REQ_OPTIONS: cmdtype = "OPTIONS"; break;
            case EVHTTP_REQ_TRACE: cmdtype = "TRACE"; break;
            case EVHTTP_REQ_CONNECT: cmdtype = "CONNECT"; break;
            case EVHTTP_REQ_PATCH: cmdtype = "PATCH"; break;
            default: cmdtype = "unknown"; break;
    }
    return cmdtype;
}
void get_get_params(struct evhttp_request *req){
    std::cout << "get params" << std::endl;
    auto uri = evhttp_request_get_evhttp_uri(req);
    const char *query = evhttp_uri_get_query(uri);
    if (query) {
       struct evkeyvalq params;
       evhttp_parse_query_str(query, &params);
       std::cout << "Query Parameters:" << std::endl;
       for (struct evkeyval *param = params.tqh_first; param; param = param->next.tqe_next) {
           std::cout << "  " << param->key << ": " << param->value << std::endl;
       }
       evhttp_clear_headers(&params);
   }
}

void get_post_params(struct evhttp_request *req){
    // 获取请求头
       struct evkeyvalq *headers = evhttp_request_get_input_headers(req);
       const char *content_type = evhttp_find_header(headers, "Content-Type");
       if (!content_type || strstr(content_type, "application/x-www-form-urlencoded") == nullptr) {
           std::cerr << "Unsupported Content-Type" << std::endl;
           evhttp_send_error(req, HTTP_BADREQUEST, "Only application/x-www-form-urlencoded is supported");
           return;
       }

       // 获取请求体
       struct evbuffer *input_buffer = evhttp_request_get_input_buffer(req);
       size_t body_length = evbuffer_get_length(input_buffer);
       char *body_data = new char[body_length + 1];
       evbuffer_copyout(input_buffer, body_data, body_length);
       body_data[body_length] = '\0'; // 确保字符串以 null 结尾

       std::cout << "Request Body: " << body_data << std::endl;

       // 解析表单数据
       struct evkeyvalq params;
       evhttp_parse_query_str(body_data, &params);

       // 打印所有 POST 参数
       std::cout << "POST Parameters:" << std::endl;
       for (struct evkeyval *param = params.tqh_first; param; param = param->next.tqe_next) {
           std::cout << param->key << ": " << param->value << std::endl;
       }

}
// HTTP请求回调函数
void http_request_handler(struct evhttp_request *req, void *ctx) {

    const int method = evhttp_request_get_command(req);
    std::cout << "Received " << get_cmd_type(method) << " request." << std::endl;
    if(method == EVHTTP_REQ_GET){
        get_get_params(req);
    }else if(method == EVHTTP_REQ_POST){
        get_post_params(req);
    }

    // 创建一个响应缓冲区
    struct evbuffer *response_buffer = evbuffer_new();
    if (!response_buffer) {
        std::cerr << "Failed to create response buffer" << std::endl;
        evhttp_send_error(req, HTTP_SERVUNAVAIL, "Server error");
        return;
    }

    // 设置响应内容
    evbuffer_add_printf(response_buffer, "Hello, World!\n");

    // 发送响应
    evhttp_send_reply(req, HTTP_OK, "OK", response_buffer);

    // 释放缓冲区
    evbuffer_free(response_buffer);
}

int main() {
    // 初始化libevent
    if(signal(SIGPIPE,SIG_IGN) == SIG_ERR){
        return -1;
    }
    struct event_base *base = event_base_new();
    if (!base) {
        std::cerr << "Failed to create event base" << std::endl;
        return 1;
    }
    evthread_use_pthreads();
    // 创建HTTP服务器
    struct evhttp *http_server = evhttp_new(base);
    if (!http_server) {
        std::cerr << "Failed to create HTTP server" << std::endl;
        return 1;
    }

    // 绑定到本地地址和端口
    if (evhttp_bind_socket(http_server, "0.0.0.0", 8080) != 0) {
        std::cerr << "Failed to bind to port 8080" << std::endl;
        return 1;
    }

    // 设置请求处理回调函数
    evhttp_set_gencb(http_server, http_request_handler, nullptr);

    std::cout << "HTTP server started on port 8080" << std::endl;

    // 进入事件循环
    event_base_dispatch(base);

    // 清理资源
    evhttp_free(http_server);
    event_base_free(base);

    return 0;
}
